package com.hmall.item.service.impl;

import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.hmall.common.exception.BizIllegalException;
import com.hmall.common.utils.BeanUtils;
import com.hmall.item.domain.dto.ItemDTO;
import com.hmall.item.domain.dto.OrderDetailDTO;
import com.hmall.item.domain.po.Item;
import com.hmall.item.mapper.ItemMapper;
import com.hmall.item.service.IItemService;
import org.springframework.stereotype.Service;

import java.util.Collection;
import java.util.List;

/**
 * 商品业务实现类
 * 继承自MyBatis-Plus的ServiceImpl，提供基础CRUD功能
 * 实现IItemService接口，处理库存扣减和批量查询等核心业务逻辑
 */
@Service
public class ItemServiceImpl extends ServiceImpl<ItemMapper, Item> implements IItemService {

    /**
     * 批量扣减商品库存（支持批量订单明细）
     * @param items 订单明细列表，每个明细包含商品ID和购买数量
     * @throws BizIllegalException 当库存不足或批量更新失败时抛出
     */
    @Override
    public void deductStock(List<OrderDetailDTO> items) {

        // MyBatis XML映射文件中的SQL语句ID
        String sqlStatement = "com.hmall.item.mapper.ItemMapper.updateStock";
        boolean updateResult = false;

        try {
            // 使用MyBatis-Plus的批量执行功能，提高库存更新效率
            // 原理：将多个update操作封装到一个SQL Session中执行
            updateResult = executeBatch(items, (sqlSession, orderDetail) ->
                    sqlSession.update(sqlStatement, orderDetail)
            );
        } catch (Exception e) {
            // 捕获更新过程中的异常（如数据库连接错误、SQL执行失败）
            throw new BizIllegalException("更新库存异常，可能是库存不足!", e);
        }

        // 检查批量更新结果：若updateResult为false，说明至少有一条更新失败（通常是库存不足）
        if (!updateResult) {
            throw new BizIllegalException("库存不足！");
        }
    }

    /**
     * 根据商品ID集合批量查询商品信息，并转换为DTO对象
     * @param ids 商品ID集合
     * @return 商品DTO列表，包含商品基本信息（如名称、价格、图片等）
     */
    @Override
    public List<ItemDTO> queryItemByIds(Collection<Long> ids) {
        // 调用MyBatis-Plus的listByIds方法批量查询商品实体
        List<Item> itemList = listByIds(ids);
        // 使用BeanUtils工具类将实体列表转换为DTO列表（属性自动映射）
        return BeanUtils.copyList(itemList, ItemDTO.class);
    }
}